﻿using BindTryParseMVC.Models;
using Microsoft.AspNetCore.Mvc;

namespace BindTryParseMVC.Controllers
{
    public class WeatherForecastController : Controller
    {
        private static readonly string[] Summaries = {
            "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
        };
        public IActionResult Index([FromRoute] Locale locale)
        {
           // var llocale = new Locale(locale);
            var weatherForecasts = Enumerable.Range(1, 5).Select(index => new WeatherForecast
            {
                Date = DateTime.Now.AddDays(index),
                TemperatureC = Random.Shared.Next(-20, 55),
                Summary = Summaries[Random.Shared.Next(Summaries.Length)]
            }).Select(wf => new WeatherForecastViewModel
            {
                Date = wf.Date.ToString("d", locale),
                TemperatureC = wf.TemperatureC,
                TemperatureF = 32 + (int)(wf.TemperatureC / 0.5556),
                Summary = wf.Summary
            });
            return View(weatherForecasts);
        }

        public IActionResult ByRange([FromQuery] DateRange range)
        {
            if (!ModelState.IsValid)
            {
                return View("Error", ModelState.Values.SelectMany(v => v.Errors));
            }
            var weatherForecasts = Enumerable.Range(1, 5).Select(index => new WeatherForecast
            {
                Date = DateTime.Now.AddDays(index),
                TemperatureC = Random.Shared.Next(-20, 55),
                Summary = Summaries[Random.Shared.Next(Summaries.Length)]
            })
                .Where(wf => DateOnly.FromDateTime(wf.Date) >= range.From
                    && DateOnly.FromDateTime(wf.Date) <= range.To)
            .Select(wf => new WeatherForecastViewModel
            {
                Date = wf.Date.ToString("d"),
                TemperatureC = wf.TemperatureC,
                TemperatureF = 32 + (int)(wf.TemperatureC / 0.5556),
                Summary = wf.Summary
            });
            var list = weatherForecasts.ToList();
            return View("Index", weatherForecasts);
        }

        public IActionResult RangeByLocale([FromRoute] string locale, [FromQuery] string range)
        {
            var localeResult = new Locale(locale);
            if (!ModelState.IsValid)
                return View("Error", ModelState.Values.SelectMany(v => v.Errors));

            if (!DateRange.TryParse(range, localeResult, out DateRange rangeResult))
            {
                ModelState.TryAddModelError(nameof(range),
                    $"Invalid date range: {range} for locale {localeResult.DisplayName}");

                return View("Error", ModelState.Values.SelectMany(v => v.Errors));
            }

            var weatherForecasts = Enumerable
                .Range(1, 5).Select(index => new WeatherForecast
                {
                    Date = DateTime.Now.AddDays(index),
                    TemperatureC = Random.Shared.Next(-20, 55),
                    Summary = Summaries[Random.Shared.Next(Summaries.Length)]
                })
                .Where(wf => DateOnly.FromDateTime(wf.Date) >= rangeResult.From
                             && DateOnly.FromDateTime(wf.Date) <= rangeResult.To)
                .Select(wf => new WeatherForecastViewModel
                {
                    Date = wf.Date.ToString("d", localeResult),
                    TemperatureC = wf.TemperatureC,
                    TemperatureF = 32 + (int)(wf.TemperatureC / 0.5556),
                    Summary = wf.Summary
                });

            return View("Index", weatherForecasts);
        }


        public IActionResult ByRangeTP([FromQuery] DateRangeTP range)
        {
            if (!ModelState.IsValid)
            {
                return View("Error", ModelState.Values.SelectMany(v => v.Errors));
            }

            var weatherForecasts = Enumerable.Range(1, 5).Select(index => new WeatherForecast
            {
                Date = DateTime.Now.AddDays(index),
                TemperatureC = Random.Shared.Next(-20, 55),
                Summary = Summaries[Random.Shared.Next(Summaries.Length)]
            })
                .Where(wf => DateOnly.FromDateTime(wf.Date) >= range.From
                && DateOnly.FromDateTime(wf.Date) <= range.To)
            .Select(wf => new WeatherForecastViewModel
            {
                Date = wf.Date.ToString("d"),
                TemperatureC = wf.TemperatureC,
                TemperatureF = 32 + (int)(wf.TemperatureC / 0.5556),
                Summary = wf.Summary
            });
            return View("Index", weatherForecasts);
        }

        /// <summary>
        /// 测试模型参数绑定
        /// https://localhost:7159/WeatherForecast/GetInstructor?instructorToUpdate.Id=123&instructorToUpdate.Name=foo
        /// https://localhost:7159/WeatherForecast/GetInstructor?Id=123&.Name=foo
        /// </summary>
        /// <param name="instructorToUpdate"></param>
        /// <returns></returns>
        public IActionResult GetInstructor(Instruction instructorToUpdate)
        {
            if (!ModelState.IsValid)
            {
                return View("Error", ModelState.Values.SelectMany(v => v.Errors));
            }
            return View("Instructor", instructorToUpdate);
        }

        public IActionResult OnPost(int?id,[Bind(Prefix ="instructor")]Instruction instructionToUpdate)
        {
            //return View("Instructor", instructionToUpdate);
            return Ok( instructionToUpdate);
        }

        /// <summary>
        /// 测试参数是集合的情况
        /// 可以接受的参数类型有：
        /// selectedCourses=1050&selectedCourses=2000
        /// selectedCourses[0]=1050&selectedCourses[1]=2000
        /// [0]=1050&[1]=2000
        /// selectedCourses[a]=1050&selectedCourses[b]=2000&selectedCourses.index=a&selectedCourses.index=b
        /// [a]=1050&[b]=2000&index=a&index=b
        /// </summary>
        /// <param name="id"></param>
        /// <param name="selectedCourses"></param>
        /// <example>
        /// {
        ///      "id": 13,
        ///      "selectedCourses": [
        ///         1050,
        ///         2000
        ///        ]
        ///  }
        /// </example>
        /// <returns></returns>
        public IActionResult TestCollections1(int? id, int[] selectedCourses)
        {
            return Ok(new { id, selectedCourses });
        }

        public IActionResult OnPost(int?id,Dictionary<int,string> selectedCourses)
        {
            return Ok(new { id, selectedCourses });
        }
    }
}
